package com.platform.qujia.pay.strategy.payment;

import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import com.platform.qujia.constantEnum.TianQuetechPayEnum;
import com.platform.qujia.param.request.AddPayOrderParam;
import com.platform.qujia.param.request.YunHuaPayParam;
import com.platform.qujia.param.request.YunHuaPayPayParams;
import com.platform.qujia.param.response.YunhuaPayRes;
import com.platform.qujia.param.response.YunhuaResponse;
import com.platform.qujia.pay.PaymentStrategy;
import com.platform.qujia.pay.strategy.YunhuaChannel;
import com.platform.qujia.pojo.PayOrder;
import com.platform.qujia.pojo.PayWay;
import com.platform.qujia.pojo.vo.StationEnterpriseCopInfoVo;
import com.platform.qujia.service.StationEnterpriseCopInfoService;
import com.platform.qujia.service.TradePaymentRecordsService;
import com.platform.qujia.utils.CodeMsg;
import com.platform.qujia.utils.exception.CustomException;
import com.yunhua.oil.common.core.utils.LocalDateUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.web.client.RestTemplate;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.Date;

/**
 * @date 2023/8/10
 */
@Component
public class YunhuaPayment implements PaymentStrategy {

    private static final Logger log = LoggerFactory.getLogger(YunhuaPayment.class);

    private final TypeReference<YunhuaResponse<YunhuaPayRes>> clazz = new TypeReference<YunhuaResponse<YunhuaPayRes>>() {};
    private String payUrl;

    @Value("${yunhua.notifyUrl}")
    private String notifyUrl;

    private YunhuaChannel yunhuaChannel;

    @Autowired
    private TradePaymentRecordsService tradePaymentRecordsService;
    @Autowired
    private RestTemplate restTemplate;

    @Resource
    private StationEnterpriseCopInfoService stationEnterpriseCopInfoService;

    public void setPayUrl(String payUrl) {
        this.payUrl = payUrl;
    }

    public void setYunhuaChannel(YunhuaChannel yunhuaChannel) {
        this.yunhuaChannel = yunhuaChannel;
    }


    @Override
    public Object beforePay(AddPayOrderParam orderParam, PayOrder payOrder, PayWay payWay) {

        if(tradePaymentRecordsService.addTradePaymentRecords(orderParam,payOrder.getOrderNo())<=0) {
            throw new CustomException("创建支付日志失败");
        }
        YunHuaPayParam yunHuaPayParam = new YunHuaPayParam();
        yunHuaPayParam.setFmno(payWay.getMno());
        yunHuaPayParam.setClientOrderNo(payOrder.getOrderNo());
        yunHuaPayParam.setClientSerialNo(payOrder.getOrderNo());
        yunHuaPayParam.setUserId(YunhuaChannel.DEFAULT_USER_ID);

        if (StringUtils.equals("pos",orderParam.getPayType())) {
            yunHuaPayParam.setPayMode(2);
            yunHuaPayParam.setPayChannel("poly_scan");
        }

        yunHuaPayParam.setTxnAmt(BigDecimal.valueOf(payOrder.getAmt()));
        yunHuaPayParam.setTxnDesc("pos扫码支付");

        YunHuaPayPayParams payParams = new YunHuaPayPayParams();

        payParams.setNotifyUrl(this.notifyUrl);
        payParams.setAuthCode(orderParam.getAuthCode());
        //机构号
        String orgCode = stationEnterpriseCopInfoService.getOrgCode(StationEnterpriseCopInfoVo.builder()
                .stationId(String.valueOf(payOrder.getStationId()))
                .enterpriseId(String.valueOf(payOrder.getEnterpriseId())).build());
        if(StringUtils.isNotBlank(orgCode)){
            payParams.setOrgCode(orgCode);
        }

        yunHuaPayParam.setPayParams(JSONObject.toJSONString(payParams));
        return yunHuaPayParam;
    }



    @Override
    public YunhuaResponse<YunhuaPayRes> doPay(AddPayOrderParam orderParam,PayOrder payOrder,PayWay payWay,Object o) {
        YunHuaPayParam payParam = (YunHuaPayParam) o;
        JSONObject jsonObject = yunhuaChannel.signParam((JSONObject)JSONObject.toJSON(payParam),payWay.getSecretKey());
        log.info("云化支付请求参数：{}",jsonObject.toJSONString());
        try{
            ResponseEntity<String> response = restTemplate.postForEntity(this.payUrl, jsonObject, String.class);
            String body = response.getBody();
            log.info("云化支付返回结果：{}", body);
            return JSONObject.parseObject(body,this.clazz);
        }catch (Exception e){
            log.error(e.getMessage(),e);
            throw new CustomException("网络异常");
        }
    }

    @Override
    public boolean checkResult(PayOrder payOrder,Object result){
        YunhuaResponse<YunhuaPayRes> response = (YunhuaResponse<YunhuaPayRes>) result;
        return StringUtils.equals(YunhuaChannel.RES_CODE_SUCCESS, response.getCode()) && response.getData().getStatus() != 4;
    }

    @Override
    public boolean checkResult2(PayOrder payOrder,Object result){
        YunhuaResponse<YunhuaPayRes> response = (YunhuaResponse<YunhuaPayRes>) result;
        Integer status = response.getData().getStatus();
        if (!StringUtils.equals(YunhuaChannel.RES_CODE_SUCCESS, response.getCode())) {
            return false;
        }
        if(status == 1 || status == 2){
            throw new CustomException(CodeMsg.TRADE_REVERSE_PAY_WAIT_MINUTE);
        }
        if(status == 3){
            return true;
        }
        throw new CustomException("支付失败");
    }

    @Override
    public TianQuetechPayEnum checkResult3(PayOrder payOrder, Object result) {
        YunhuaResponse<YunhuaPayRes> response = (YunhuaResponse<YunhuaPayRes>) result;
        if (response == null || response.getData() == null) {
            return TianQuetechPayEnum.PAY_FAIL;
        }
        Integer status = response.getData().getStatus();
        if (!StringUtils.equals(YunhuaChannel.RES_CODE_SUCCESS, response.getCode())) {
            return TianQuetechPayEnum.PAY_FAIL;
        }
        if(status == 1 || status == 2){
            return TianQuetechPayEnum.PAY_PAYING;
        }
        if(status == 3){
            return TianQuetechPayEnum.PAY_SUCCESS;
        }
        return TianQuetechPayEnum.PAY_FAIL;
    }

    @Override
    public void postPay(PayOrder payOrder,Object result) {
        if (result == null) {
            return;
        }
        YunhuaResponse<YunhuaPayRes> response = (YunhuaResponse<YunhuaPayRes>) result;
//        YunhuaPayRes res = response.getData();
        tradePaymentRecordsService.updateYunHuaPayInfo(response);

//        payOrder.setTransactionId(res.getTransPayNo());
//        payOrder.setMerchantsNumber(res.getTransInfoNo());

//        if (res.getStatus() == 3) {
//            String payTimeStr = res.getPayTime();
//            if (StringUtils.isNotBlank(payTimeStr)) {
//                LocalDateTime payTime = LocalDateTime.parse(payTimeStr);
//                Date date = LocalDateUtils.localDateTimeToDate(payTime);
//                payOrder.setPayDate(date);
//            }
//            payOrder.setStatus(TianQuetechPayEnum.PAY_SUCCESS.getValue().toString());
//        }
    }

    @Override
    public void syncPostPay(PayOrder payOrder, Object result) {

    }
}
